package com.gotye.particlesystem.objects;

import android.opengl.GLES20;

import com.gotye.particlesystem.data.VertexArray;
import com.gotye.particlesystem.programs.TextureShaderProgram;

import java.nio.ByteBuffer;
import java.nio.ByteOrder;
import java.nio.FloatBuffer;

/**
 * Created by Michael.Ma on 2016/6/28.
 */
public class Cube {
    private VertexArray vertexArray;
    private ByteBuffer indexArray;

    private static final int POSITION_COMPONENT_COUNT = 3;
    private static final int TEXTURE_COORDINATES_COMPONENT_COUNT = 2;
    private static final int NORMAL_COMPONENT_COUNT = 3;
    private static final int BYTES_PER_FLOAT = 4;
    private static final int STRIDE =
            (POSITION_COMPONENT_COUNT + TEXTURE_COORDINATES_COMPONENT_COUNT + NORMAL_COMPONENT_COUNT) * BYTES_PER_FLOAT;

    public Cube() {
        /*vertexArray = new VertexArray(new float[] {
                -1,  1,  1, 0, 1, // (0) Top-left near
                 1,  1,  1, 1, 1, // (1) Top-right near
                -1, -1,  1, 0, 0, // (2) Bottom-left near
                 1, -1,  1, 1, 0, // (3) Bottom-right near
                -1,  1, -1, 0, 1, // (4) Top-left far
                 1,  1, -1, 1, 1, // (5) Top-right far
                -1, -1, -1, 0, 0, // (6) Bottom-left far
                 1, -1, -1, 1, 0 // (7) Bottom-right far
        });*/

        vertexArray = new VertexArray(new float[] {
                // vertex(x y z) texture(s t) normal(x y z)

                // Front
                 1,  1,  1, 1, 1, 0, 0,  1, // (1) Top-right near
                 1, -1,  1, 1, 0, 0, 0,  1, // (3) Bottom-right near
                -1,  1,  1, 0, 1, 0, 0,  1, // (0) Top-left near
                -1, -1,  1, 0, 0, 0, 0,  1, // (2) Bottom-left near

                // Back
                -1,  1, -1, 1, 1, 0, 0, -1, // (4) Top-left far
                -1, -1, -1, 1, 0, 0, 0, -1, // (6) Bottom-left far
                 1,  1, -1, 0, 1, 0, 0, -1, // (5) Top-right far
                 1, -1, -1, 0, 0, 0, 0, -1, // (7) Bottom-right far

                // Left
                -1,  1,  1, 1, 1, -1, 0, 0, // (0) Top-left near
                -1, -1,  1, 1, 0, -1, 0, 0, // (2) Bottom-left near
                -1,  1, -1, 0, 1, -1, 0, 0, // (4) Top-left far
                -1, -1, -1, 0, 0, -1, 0, 0, // (6) Bottom-left far

                // Right
                 1,  1, -1, 1, 1,  1, 0, 0, // (5) Top-right far
                 1, -1, -1, 1, 0,  1, 0, 0, // (7) Bottom-right far
                 1,  1,  1, 0, 1,  1, 0, 0, // (1) Top-right near
                 1, -1,  1, 0, 0,  1, 0, 0, // (3) Bottom-right near

                // Top
                 1,  1, -1, 1, 1, 0, 1, 0, // (5) Top-right far
                 1,  1,  1, 1, 0, 0, 1, 0, // (1) Top-right near
                -1,  1, -1, 0, 1, 0, 1, 0, // (4) Top-left far
                -1,  1,  1, 0, 0, 0, 1, 0, // (0) Top-left near

                // Bottom
                -1, -1, -1, 1, 1, 0, -1, 0, // (6) Bottom-left far
                -1, -1,  1, 1, 0, 0, -1, 0, // (2) Bottom-left near
                 1, -1, -1, 0, 1, 0, -1, 0, // (7) Bottom-right far
                 1, -1,  1, 0, 0, 0, -1, 0, // (3) Bottom-right near
        });

        indexArray = ByteBuffer.allocateDirect(6 * 6)
                .put(new byte[] {
                        // Front
                        1, 3, 0,
                        0, 3, 2,

                        // Back
                        4, 6, 5,
                        5, 6, 7,

                        // Left
                        0, 2, 4,
                        4, 2, 6,

                        // Right
                        5, 7, 1,
                        1, 7, 3,

                        // Top
                        5, 1, 4,
                        4, 1, 0,

                        // Bottom
                        6, 2, 7,
                        7, 2, 3
                });
        indexArray.position(0);
    }

    public void bindData(TextureShaderProgram textureShaderProgram) {
        vertexArray.setVertexAttribPointer(
                0,
                textureShaderProgram.getPositionAttributeLocation(),
                POSITION_COMPONENT_COUNT,
                STRIDE);
        vertexArray.setVertexAttribPointer(
                POSITION_COMPONENT_COUNT,
                textureShaderProgram.getTextureCoordinatesAttributeLocation(),
                TEXTURE_COORDINATES_COMPONENT_COUNT,
                STRIDE);
        vertexArray.setVertexAttribPointer(
                POSITION_COMPONENT_COUNT + TEXTURE_COORDINATES_COMPONENT_COUNT,
                textureShaderProgram.getNormalAttributeLocation(),
                NORMAL_COMPONENT_COUNT,
                STRIDE);
    }

    public void draw() {
        //GLES20.glDrawElements(GLES20.GL_TRIANGLES, 36, GLES20.GL_UNSIGNED_BYTE, indexArray);

        for (int face=0;face<6;face++) {
            GLES20.glDrawArrays(GLES20.GL_TRIANGLE_STRIP, face * 4, 4);
        }
    }
}
